package com.example.ccj.b.c.recycler;

import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.util.AttributeSet;
import android.view.KeyEvent;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.view.inputmethod.EditorInfo;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.RelativeLayout;
import android.widget.TextView;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.recyclerview.widget.DefaultItemAnimator;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;


import com.example.ccj.R;
import com.example.ccj.b.c.custom.IMRadioButtonListener;
import com.example.ccj.b.c.custom.adapter.OptionMode;
import com.example.ccj.b.c.custom.adapter.OptionSelectListener;
import com.example.ccj.b.c.custom.adapter.OptionChoiceRecyclerAdapter;
import com.example.ccj.u.ActivityUtils;
import com.example.ccj.u.KeyboardUtils;
import com.example.ccj.u.LogUtils;
import com.scwang.smart.refresh.layout.SmartRefreshLayout;
import com.scwang.smart.refresh.layout.listener.OnLoadMoreListener;
import com.scwang.smart.refresh.layout.listener.OnRefreshListener;

import java.util.ArrayList;
import java.util.List;

/**
 * RecyclerView模板
 */
public class BaseRecycler<T> extends RelativeLayout {
    private static final String TAG = "BaseRecycler";
    private RecyclerView recyclerView;
    private SmartRefreshLayout refreshLayout;//下拉刷新
    //正在加载控件 搜索控件
    private LinearLayout loadData,search;
    //空数据提示  错误提示
    private TextView emptyData,errorData;
    //搜索文本框
    private EditText searchText;
    //搜索按钮
    private ImageView searchImg;
    private RecyclerView.Adapter<?> adapter;
    //数据
    private List<T> defaultData;


    private OptionChoiceRecyclerAdapter optionChoiceRecyclerAdapter;

    //当前状态
    int thisMode = DATA_STATE_LOAD;

    //空数据提示
    private String nullDataTip = "没有数据！";

    public static final int DATA_STATE_NULL = 1;
    public static final int DATA_STATE_LOAD = 2;
    public static final int DATA_STATE_LOAD_ERROR = 3;
    public static final int DATA_STATE_OK = 4;


    public BaseRecycler(Context context){
        super(context);
        init();
    }

    public BaseRecycler(Context context, @Nullable AttributeSet attrs) {
        super(context, attrs);
        init();
    }

    private void init(){
        LayoutInflater.from(getContext()).inflate(R.layout.base_recycler,this);
        recyclerView = findViewById(R.id.base_recycler_rec);
        recyclerView.setLayoutManager(new LinearLayoutManager(getContext()));

        recyclerView.setItemAnimator(new DefaultItemAnimator());
        refreshLayout = findViewById(R.id.base_recycler_refreshLayout);
        search = findViewById(R.id.base_recycler_search);
        searchText = findViewById(R.id.base_recycler_search_text);
        searchImg = findViewById(R.id.base_recycler_search_img);
        search.setVisibility(View.GONE);
        refreshLayout.setEnableRefresh(false);
        refreshLayout.setEnableLoadMore(false);

        loadData = findViewById(R.id.base_recycler_load_data);//正在加载
        emptyData = findViewById(R.id.base_recycler_empty_data);//空数据
        emptyData.setText(nullDataTip);
        errorData = findViewById(R.id.base_recycler_get_data_error);//错误数据
        adapter = new DefaultAdapter<>();
        defaultData = new ArrayList<>();
        //设置动画
        setAnimator();
    }



    public void setControlState(int state){
        thisMode = state;
        post(() -> {
            switch (state) {
                case DATA_STATE_NULL:
                    loadData.setVisibility(View.GONE);
                    emptyData.setVisibility(View.VISIBLE);
                    errorData.setVisibility(View.GONE);
                    break;
                case DATA_STATE_LOAD:
                    loadData.setVisibility(View.VISIBLE);
                    emptyData.setVisibility(View.GONE);
                    errorData.setVisibility(View.GONE);
                    break;
                case DATA_STATE_LOAD_ERROR:
                    loadData.setVisibility(View.GONE);
                    emptyData.setVisibility(View.GONE);
                    errorData.setVisibility(View.VISIBLE);
                    break;
                case DATA_STATE_OK:
                    loadData.setVisibility(View.GONE);
                    emptyData.setVisibility(View.GONE);
                    errorData.setVisibility(View.GONE);
                    break;
            }
        });
    }

    private void setDataState(){
        if (thisMode == DATA_STATE_LOAD) return;
        if (defaultData == null || defaultData.isEmpty()) {
            setControlState(DATA_STATE_NULL);
        } else {
            setControlState(DATA_STATE_OK);
        }
    }

    /**
     * 设置分割线
     */
    public void setItemDecoration(@NonNull RecyclerView.ItemDecoration decor){
        recyclerView.addItemDecoration(decor);
    }

    /**
     * 设置默认分割线
     */
    public void setItemDecoration(){
        recyclerView.addItemDecoration(new DividerItemDecoration(getContext(), 1));
    }

    /**
     * 设置默认Adapter
     * @param defaultData 数据
     * @param layout 布局文件
     * @param defaultAdapterOnBind  自定义布局加载回调
     */
    public void setDefaultAdapter(List<T> defaultData,int layout,DefaultAdapterOnBind<T> defaultAdapterOnBind){
        this.defaultData = defaultData;
        setDataState();
        adapter = new DefaultAdapter<>(this.defaultData,layout,defaultAdapterOnBind);
        setAdapter(adapter);
    }

    /**
     * 设置默认Adapter带右滑菜单功能
     * @param layout 布局文件
     * @param defaultData 数据
     * @param functionModels 右滑菜单功能按钮定义
     * @param defaultAdapterOnBind 自定义布局加载回调
     */
    public void setDefaultAdapter(List<T> defaultData,List<FunctionModel<T>> functionModels,int layout,DefaultAdapterOnBind<T> defaultAdapterOnBind){
        this.defaultData = defaultData;
        setDataState();
        adapter = new DefaultAdapter<>(this.defaultData,functionModels,layout,defaultAdapterOnBind);
        if (functionModels != null && functionModels.size() > 0 ) showRightFunction();
        setAdapter(adapter);
    }

    /**
     * 设置选项模式
     * @param defaultData 默认数据String数组
     * @param isReadOnly 选项是否只读
     * @param optionMode 选项模式 单选 or 多选
     * @param selectListener 选择后返回
     */
    public void setOptionChoiceAdapter(List<T> defaultData,boolean isReadOnly , OptionMode optionMode, IMRadioButtonListener<T> selectListener){
        optionChoiceRecyclerAdapter = new OptionChoiceRecyclerAdapter<>(defaultData,isReadOnly,optionMode,selectListener);
        setDataState();
        setAdapter(optionChoiceRecyclerAdapter);
    }

    public void setOptionChoiceReadOnly(boolean isReadOnly){
        if (optionChoiceRecyclerAdapter == null) {
            LogUtils.e("修改选项模式失败，该Adapter不是单选项或多选项，你需要首先调用setOptionChoiceAdapter方法设置");
            return;
        }
        optionChoiceRecyclerAdapter.setOptionChoiceReadOnly(isReadOnly);
    }

    /**
     * 显示右侧划出功能
     */
    private void showRightFunction(){
        if (adapter != null && adapter instanceof DefaultAdapter) {
            //触摸监听
            recyclerView.addOnItemTouchListener(new ItemSlideHelper(getContext(), new ItemSlideHelper.Callback() {
                @Override
                public int getHorizontalRange(RecyclerView.ViewHolder holder) {
                    if (holder.itemView instanceof LinearLayout) {
                        ViewGroup viewGroup = (ViewGroup) holder.itemView;
                        int count = viewGroup.getChildCount();
                        int resultWieth = 0;
                        //返回左移的宽度
                        if (count >1) {
                            //略过第一个控件，因为第一个一般是主体
                            for (int i=1;i<count;i++) {
                                if (viewGroup.getChildAt(i).getVisibility() == View.VISIBLE) {
                                    resultWieth += viewGroup.getChildAt(i).getLayoutParams().width;
                                }
                            }
                            return resultWieth;
                        }
                    }
                    return 0;
                }

                @Override
                public RecyclerView.ViewHolder getChildViewHolder(View childView) {
                    return recyclerView.getChildViewHolder(childView);
                }

                @Override
                public View findTargetView(float x, float y) {
                    return recyclerView.findChildViewUnder(x, y);
                }
            }));
        } else {
            LogUtils.e("设置右侧功能键划出失败 adapter为空或者其不是默认的布局！");
        }
    }

    /**
     * 添加默认动画
     */
    public void setAnimator(){
        DefaultItemAnimator defaultItemAnimator = new DefaultItemAnimator();
        defaultItemAnimator.setAddDuration(200);
        defaultItemAnimator.setRemoveDuration(200);
        recyclerView.setItemAnimator(defaultItemAnimator);
    }

    /**
     * 添加自定义动画
     */
    public void setAnimator(DefaultItemAnimator defaultItemAnimator){
        if (defaultItemAnimator == null) setAnimator();
        else recyclerView.setItemAnimator(defaultItemAnimator);
    }

    /**
     * 添加自定义Adapter
     */
    public void setAdapter(@Nullable RecyclerView.Adapter<?> adapter){
        if (adapter == null || adapter.getItemCount() < 1) {
            setControlState(DATA_STATE_NULL);
        } else {
            setControlState(DATA_STATE_OK);
        }
        this.adapter = adapter;
        recyclerView.post(() -> recyclerView.setAdapter(adapter));
    }


    /**
     * 添加自定义Adapter
     */
    public void setAdapter(@NonNull List<T> data,@Nullable RecyclerView.Adapter<?> adapter){
        if (adapter == null || adapter.getItemCount() < 1) {
            setControlState(DATA_STATE_NULL);
        } else {
            setControlState(DATA_STATE_OK);
        }
        this.adapter = adapter;
        this.defaultData = data;
        recyclerView.post(() -> recyclerView.setAdapter(adapter));
    }

    /**
     * 添加需要网络加载数据的Adapter
     */
    public void setLoadDataAdapter(@NonNull List<T> data,@Nullable RecyclerView.Adapter<?> adapter){
        if (adapter == null) {
            setControlState(DATA_STATE_NULL);
        }
        this.adapter = adapter;
        this.defaultData = data;
        recyclerView.post(() -> recyclerView.setAdapter(adapter));
    }

    public void LoadOver(){
        thisMode = DATA_STATE_OK;
        setDataState();
    }

    /**
     * 设置布局样式
     */
    public void setLayoutManager(@Nullable RecyclerView.LayoutManager layout){
        recyclerView.setLayoutManager(layout);
    }

    //下拉刷新
    public void setDownRefresh(OnRefreshListener onRefreshListener){
        refreshLayout.setEnableRefresh(true);
        refreshLayout.setOnRefreshListener(onRefreshListener);
    }

    //上拉加载更多
    public void setUpLoadMore(OnLoadMoreListener onLoadMoreListener){
        refreshLayout.setEnableLoadMore(true);
        refreshLayout.setOnLoadMoreListener(onLoadMoreListener);
    }

    /**
     * 显示新的搜索界面activity
     * @param tag 新的搜索界面所需要的标记 用于获取历史数据
     */
    public void showNewSearchActivity(int tag, Activity activity){
        search.setVisibility(View.VISIBLE);
        searchText.setOnClickListener(getSearchOnclick(tag,activity));
        searchImg.setOnClickListener(getSearchOnclick(tag,activity));
    }

    /**
     * 跳转新的搜索界面
     * @param tag 新的搜索界面所需要的标记 用于获取历史数据
     * @return 点击事件
     */
    private OnClickListener getSearchOnclick(int tag, Activity activity){
        return new OnClickListener() {
            @Override
            public void onClick(View view) {
                Intent intent = new Intent(view.getContext(),activity.getClass());
                intent.putExtra("type",tag);
                ActivityUtils.getTopActivity().startActivityForResult(intent,tag);
            }
        };
    }

    /**
     * 显示搜索控件
     * @param changedListener 搜索
     */
    public void showSearchControl(SearchTextChangedLinsener changedListener){
        search.setVisibility(View.VISIBLE);
        //edittext输入监听  注意该方法需要通过敲击回车键才会有所监听返回
        searchText.setOnEditorActionListener(new TextView.OnEditorActionListener() {
            @Override
            public boolean onEditorAction(TextView textView, int actionId, KeyEvent keyEvent) {
                if (actionId == EditorInfo.IME_ACTION_SEARCH) {
                    KeyboardUtils.hideSoftInput(textView);//隐藏软键盘
                    changedListener.searchTextChange(textView.getText().toString());
                }
                return false;
            }
        });
        searchImg.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View v) {
                changedListener.searchButtonClick(searchText.getText().toString());
            }
        });
    }

    /**
     * 设置错误提示
     * @param value 错误信息
     */
    public void setErrorData(String value){
        errorData.setVisibility(VISIBLE);
        errorData.setText(value);
    }

    private boolean isIndexOutOfBounds(int position){
        return position >= adapter.getItemCount();
    }

    /**
     * 刷新某条数据
     * @param position 数据编号
     */
    public void refreshData(int position){
        if (isIndexOutOfBounds(position)) {
            LogUtils.e(TAG,"刷新数据失败,下标越界："+position+",当前最大下标值:"+(adapter.getItemCount()-1));
        }
        recyclerView.post(new Runnable() {
            @Override
            public void run() {
                adapter.notifyItemChanged(position);
            }
        });
    }

    /**
     * 固定位置插入数据
     * @param position 数据编号
     * @param data 数据
     */
    public void addDataOnFix(int position,T data){
        if (data == null) {
            LogUtils.e(TAG,"固定位置添加数据失败,传入数据为null");
            return;
        }
        if (!isIndexOutOfBounds(position)) {
            defaultData.add(position,data);
        } else {
            defaultData.add(data);
            position = defaultData.size()-1;
        }
        int finalPos = position;
        recyclerView.post(() -> {
            adapter.notifyItemInserted(finalPos);//通知演示插入动画
            adapter.notifyItemRangeChanged(finalPos,defaultData.size()-finalPos);//通知数据与界面重新绑定
            recyclerView.scrollToPosition(finalPos);
        });
        setDataState();
    }

    /**
     * 头插数据
     * @param data  数据
     */
    public void addDataOnHead(T data){
        if (data == null) {
            LogUtils.e(TAG,"头部添加数据失败,传入数据为null");
            return;
        }
        defaultData.add(0,data);
        recyclerView.post(() -> {
            adapter.notifyItemInserted(0);//通知演示插入动画
            adapter.notifyItemRangeChanged(0,defaultData.size());//通知数据与界面重新绑定
            recyclerView.scrollToPosition(0);
        });
        setDataState();
    }


    /**
     * 尾插数据
     * @param data 数据
     */
    public void addDataOnTail(T data){
        if (data == null) {
            LogUtils.e(TAG,"尾部添加数据失败,传入数据为null");
            return;
        }
        defaultData.add(data);
        recyclerView.post(() -> {
            adapter.notifyItemRangeChanged(defaultData.size()-1,1);//通知演示插入动画
            recyclerView.scrollToPosition(defaultData.size());
        });
        setDataState();
    }

    /**
     * 删除数据
     * @param position 数据编号
     */
    public void removeData(int position){
        if (isIndexOutOfBounds(position)) {
            LogUtils.e(TAG,"删除数据失败,下标越界："+position+",当前最大下标值:"+(adapter.getItemCount()-1));
            return;
        }
        defaultData.remove(position);
        recyclerView.post(() -> {
            adapter.notifyItemRemoved(position);
            adapter.notifyItemRangeChanged(0,defaultData.size());//通知数据与界面重新绑定
        });
        setDataState();
    }

    /**
     * 删除数据
     * @param t 数据编号
     */
    public void removeData(T t){
        if (defaultData.contains(t)) {
            int i = defaultData.indexOf(t);
            defaultData.remove(t);
            recyclerView.post(() -> {
                adapter.notifyItemRemoved(i);
                adapter.notifyItemRangeChanged(0,defaultData.size());//通知数据与界面重新绑定
            });
            setDataState();
        }
    }


    /**
     * 删除数据
     */
    public void removeAllData(){
        int size = defaultData.size();
        defaultData.clear();
        recyclerView.post(() -> {
            adapter.notifyItemRangeChanged(0,size);
        });
        setDataState();
    }


    /**
     * 批量添加数据
     * @param data 数据
     */
    public void addDatas(List<T> data){
        //是否为空
        if (data == null) {
            LogUtils.e(TAG,"添加多条数据，数据不可为空");
            return;
        }
        //是否没有数据
        if (data.size() < 1) {
            LogUtils.e(TAG,"添加多条数据，传入参数无数据");
            return;
        }
        recyclerView.post(() -> {
            int oldSize = defaultData.size();
            defaultData.addAll(data);
            adapter.notifyItemRangeInserted(oldSize, data.size());
            setDataState();
        });
    }

    /**
     * 清空所有数据
     */
    public void clearDataAll(){
        recyclerView.post(new Runnable() {
            @Override
            public void run() {
                if (!defaultData.isEmpty()) {
                    int previousSize = defaultData.size();
                    defaultData.clear();
                    adapter.notifyItemRangeRemoved(0, previousSize);
                    setDataState();
                }
            }
        });
    }


    /**
     * 替换数据，刷新操作
     * @param data 数据
     */
    public void replaceData(@NonNull List<T> data){
        //是否没有数据
        recyclerView.post(() -> {
            defaultData.clear();
            defaultData.addAll(data);
            adapter.notifyDataSetChanged();
            setDataState();
        });
    }

    public RecyclerView.Adapter<?>  getAdapter(){
        return recyclerView.getAdapter();
    }
    public RecyclerView getRecyclerView() {
        return recyclerView;
    }
    public void setRefreshLayout(SmartRefreshLayout refreshLayout) {
        this.refreshLayout = refreshLayout;
    }
    public void setRecyclerView(RecyclerView recyclerView) {
        this.recyclerView = recyclerView;
    }
    public SmartRefreshLayout getRefreshLayout() {
        return refreshLayout;
    }

    public LinearLayout getLoadData() {
        return loadData;
    }

    public void setLoadData(LinearLayout loadData) {
        this.loadData = loadData;
    }

    public LinearLayout getSearch() {
        return search;
    }

    public void setSearch(LinearLayout search) {
        this.search = search;
    }

    public TextView getEmptyData() {
        return emptyData;
    }

    public void setEmptyData(TextView emptyData) {
        this.emptyData = emptyData;
    }

    public TextView getErrorData() {
        return errorData;
    }

    public void setErrorData(TextView errorData) {
        this.errorData = errorData;
    }

    public EditText getSearchText() {
        return searchText;
    }

    public void setSearchText(EditText searchText) {
        this.searchText = searchText;
    }

    public ImageView getSearchImg() {
        return searchImg;
    }

    public void setSearchImg(ImageView searchImg) {
        this.searchImg = searchImg;
    }

    public List<T> getDefaultData() {
        return defaultData;
    }

    public void setDefaultData(List<T> defaultData) {
        this.defaultData = defaultData;
    }

    public void setNullDataTip(String nullDataTip) {
        this.nullDataTip = nullDataTip;
    }

}
